package com.symbio.ishenapi.order.controller;


import com.jfinal.kit.StrKit;
import com.jfinal.weixin.sdk.api.PaymentApi;
import com.jfinal.weixin.sdk.kit.IpKit;
import com.jfinal.weixin.sdk.kit.PaymentKit;
import com.symbio.ishenapi.common.controller.BaseController;
import com.symbio.ishenapi.order.model.TmPaymentRecord;
import com.symbio.ishenapi.order.model.TmServiceOrder;
import com.symbio.ishenapi.order.tencent.common.HttpsRequest;
import com.symbio.ishenapi.order.tencent.common.Util;
import com.symbio.ishenapi.order.tencent.common.report.protocol.UniCallbackResData;
import com.symbio.ishenapi.order.tencent.protocol.pay_protocol.AppPayReqData;
import com.symbio.ishenapi.order.weixinpay.*;
import io.jboot.utils.StringUtils;
import io.jboot.web.controller.annotation.RequestMapping;
import org.apache.commons.lang.time.DateUtils;
import org.jdom.JDOMException;


import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.security.*;
import java.util.*;


@RequestMapping("/weiXinPay")
public class WxpayController extends BaseController {

    String randomString = PayCommonUtil.getRandomString(32);

    //支付成功后的回调函数
    public static String wxnotify = "http://com.zhuohuicalss/weiXinPay/notifyWeiXinPay";

    public WxpayController() {
        System.out.println("MainController构造函数");
    }


    /**
     * 此函数会被执行多次，如果支付状态已经修改为已支付，则下次再调的时候判断是否已经支付，如果已经支付了，则什么也执行
     *
     * @param
     * @param
     * @return
     * @throws IOException
     * @throws //JDOMException
     */
    public void notifyWeiXinPay() throws IOException, JDOMException {
        System.out.println("微信支付回调");
        HttpServletRequest request = getRequest();
        HttpServletResponse response = getResponse();
        InputStream inStream = request.getInputStream();
        ByteArrayOutputStream outSteam = new ByteArrayOutputStream();
        byte[] buffer = new byte[1024];
        int len = 0;
        while ((len = inStream.read(buffer)) != -1) {
            outSteam.write(buffer, 0, len);
        }
        String resultxml = new String(outSteam.toByteArray(), "utf-8");
        Map<String, String> params = PayCommonUtil.doXMLParse(resultxml);
        outSteam.close();
        inStream.close();


        Map<String, String> return_data = new HashMap<String, String>();
        if (!PayCommonUtil.isTenpaySign(params)) {
            // 支付失败
            return_data.put("return_code", "FAIL");
            return_data.put("return_msg", "return_code不正确");
            String str = StringUtil.GetMapToXML(return_data);
            renderJsonRet(str);
            return;
        } else {
            System.out.println("===============付款成功==============");
            // ------------------------------
            // 处理业务开始
            // ------------------------------
            // 此处处理订单状态，结合自己的订单数据完成订单状态的更新
            // ------------------------------

            String total_fee = params.get("total_fee");
            double v = Double.valueOf(total_fee) / 100;
            String out_trade_no = String.valueOf(Long.parseLong(params.get("out_trade_no").split("O")[0]));
        /*    Date accountTime = DateUtil.stringtoDate(params.get("time_end"), "yyyyMMddHHmmss");
            String ordertime = DateUtil.dateToString(new Date(), "yyyy-MM-dd HH:mm:ss");
            String totalAmount = String.valueOf(v);
            String appId = params.get("appid");
            String tradeNo = params.get("transaction_id");*/
            TmServiceOrder serviceOrder = new TmServiceOrder();
            serviceOrder.setId(new BigInteger(out_trade_no));
            //在这处理业务逻辑
            //TmServiceOrder tso = new TmServiceOrder();
            TmServiceOrder tmServiceOrder = TmServiceOrder.dao.findOne(serviceOrder);
            if (tmServiceOrder == null ) {
                return_data.put("return_code", "FAIL");
                return_data.put("return_msg", "没有查到该订单");
                String str = StringUtil.GetMapToXML(return_data);
                renderJsonRet(str);
                return;
            }
            try {
                //支付成功处理支付业务
                int result = TmServiceOrder.dao.updateOrderStatus(tmServiceOrder.getId(), "18918005", "2");
                if (result == 1) {
                    return_data.put("return_code", "SUCCESS");
                    return_data.put("return_msg", "OK");
                    String str = StringUtil.GetMapToXML(return_data);
                    renderJsonRet(str);
                    return;
                }
            } catch (Exception e) {
                e.printStackTrace();
                return_data.put("return_code", "FAIL");
                return_data.put("return_msg", "更新订单状态失败！");
                String str = StringUtil.GetMapToXML(return_data);
                renderJsonRet(str);
                return;
            }
        }
        return_data.put("return_code", "FAIL");
        return_data.put("return_msg", "支付失败！");
        String str = StringUtil.GetMapToXML(return_data);
        renderJsonRet(str);
        return;
    }



    /**
     * 统一下单
     * 应用场景：商户系统先调用该接口在微信支付服务后台生成预支付交易单，返回正确的预支付交易回话标识后再在APP里面调起支付。
     *
     * @return
     * @paramsym
     */
    public void place() {
        String orderId= getPara("order_id");//订单id
        String total_fee= getPara("total_fee");//金额
        String out_trade_no= getPara("out_trade_no");//订单编号
        //==================================
        String appId = "wx2f5397300a254714";
        String mchId = "1519513811";
        String key = "zaq1xsw2cde3vfr4bgt5nhy6mju7lkio";
        String nonceStr = System.nanoTime() + "";

        //判断参数是否为空
        if(orderId == null || total_fee == null || out_trade_no == null){
            renderJsonError(40003,"参数");
            return;
        }

        //判断订单是否为空
        TmServiceOrder order = TmServiceOrder.dao.getById(new BigInteger(orderId));
        if(order == null){
            renderJsonError(40003,"订单");
            return;
        }

        Map<String, String> params = new HashMap<String, String>();
        params.put("appid", appId);
        params.put("mch_id", mchId);
        params.put("nonce_str", nonceStr);
        params.put("body", "订单测试");
        params.put("out_trade_no", out_trade_no);
        params.put("total_fee", total_fee);
        String ip = IpKit.getRealIp(getRequest());
        if (StrKit.isBlank(ip)) {
            ip = "127.0.0.1";
        }

        params.put("spbill_create_ip", ip);
        params.put("notify_url", "http://111.198.66.210:7101/weiXinPay/notifyWeiXinPay");
        params.put("trade_type", "APP");
        params.put("sign_type", "MD5");
        //生成签名方法（一次）
        String sign = PaymentKit.createSign(params, key);
        params.put("sign", sign);
        String xmlResult = PaymentApi.pushOrder(params);

        System.out.println(xmlResult);
        Map<String, String> result = PaymentKit.xmlToMap(xmlResult);

        String return_code = result.get("return_code");
        String return_msg = result.get("return_msg");
        if (StrKit.isBlank(return_code) || !"SUCCESS".equals(return_code)) {
            renderText(return_msg);
            return;
        }
        String result_code = result.get("result_code");
        if (StrKit.isBlank(result_code) || !"SUCCESS".equals(result_code)) {
            renderText(return_msg);
            return;
        }
        String prepay_id = result.get("prepay_id");
        //保存支付记录表
        TmPaymentRecord record = new TmPaymentRecord();
        record.setOrderId(new BigInteger(orderId));
        record.setPayPrice(Double.parseDouble(total_fee));
        record.setPayType(1L);
        record.setPrepayId(prepay_id);
        record.setStatus(1L);
        record.setCreateTime(new Date());
        record.save();


        // 以下字段在return_code 和result_code都为SUCCESS的时候有返回

        Map<String, String> data = new HashMap<String, String>();
        data.put("appid", appId);
        data.put("partnerid", mchId);
        data.put("prepayid", prepay_id);
        data.put("package", "Sign=WXPay");
        data.put("noncestr", nonceStr);
        data.put("timestamp",System.currentTimeMillis()/1000+"");
        //再次签名（二次）
        String appSign = PaymentKit.createSign(data, key);
        data.put("sign", appSign);
        data.put("outtradeno", out_trade_no);

        renderJsonRet(data);
    }


    public UniCallbackResData places(AppPayReqData postdata) {
        String url = Configure.getUNIFIED_ORDER_API();
        UniCallbackResData rsModel = null;
        try {

            HttpsRequest hsq = null;
            try {
                hsq = new HttpsRequest();
            } catch (Exception e) {
                //logger.info("你好：" + e.getMessage());
                e.printStackTrace();
            }
            String result = hsq.sendPost(url, postdata);
            System.out.println("==================="+result);
            rsModel = (UniCallbackResData) Util.getObjectFromXML(result, UniCallbackResData.class);
        } catch (UnrecoverableKeyException | KeyManagementException | NoSuchAlgorithmException | KeyStoreException
                | IOException e) {
            System.out.println("微信支付下单出错！：" + e.getMessage());
            return null;
        } catch (Exception e) {
            System.out.println("微信支付下单出错：" + e.getMessage());
            return null;
        }
        return rsModel;
    }
}
